Описание проекта: Я аналитик в мобильном приложении по продаже продуктов питания. Дизайнеры захотели поменять шрифты во всём приложении, а менеджеры испугались, что пользователям будет непривычно. Договорились принять решение по результатам A/A/B-теста. Пользователей разбили на 3 группы: 2 контрольные со старыми шрифтами и одну экспериментальную — с новыми.
Описание данных Каждая запись в логе — это действие пользователя, или событие:
Цель исследования: Нужно изучить воронку продаж, ответить на вопросы, исследовать результаты А/А/В эксперимента и выявить какой шрифт лучше.
Ход исследования:
Общий вывод: резюмирование полученных результатов, формулировка ключевых выводов.
# импортируем библиотеки pandas, matplot, numpy, scipy
import pandas as pd
import numpy as np
import seaborn as sns
import datetime as dt
from matplotlib import pyplot as plt
from scipy import stats as st
import math as mth
import plotly.express as px
# устанавливаем отображение количества столбцов
pd.options.display.max_columns = 40
# устанавливаем отображение полного текста в ячейке
pd.set_option('display.max_colwidth', None)
# устанавливаем отображение чисел с двумя знаками после запятой
pd.set_option('display.float_format', '{:.2f}'.format)
# открываем файл
logs = pd.read_csv('/Users/ildushisamov/Desktop/projects/sborka_2/logs_exp.csv', sep='\t')
def my_func(x):
print('-'*15, 'Исходный датафрейм', '-'*15)
display(x.head())
print('')
print('')
print('-'*15, 'Общая информация о датафрейме', '-'*15)
print('')
print('')
x.info()
print('-'*15, 'Количество явных дубликатов в датафрейме', '-'*15)
display(x.duplicated().sum())
print('')
print('')
print('-'*15, 'Описательная статистика', '-'*15)
display(x.describe())
my_func(logs)
--------------- Исходный датафрейм ---------------
| EventName | DeviceIDHash | EventTimestamp | ExpId | |
|---|---|---|---|---|
| 0 | MainScreenAppear | 4575588528974610257 | 1564029816 | 246 |
| 1 | MainScreenAppear | 7416695313311560658 | 1564053102 | 246 |
| 2 | PaymentScreenSuccessful | 3518123091307005509 | 1564054127 | 248 |
| 3 | CartScreenAppear | 3518123091307005509 | 1564054127 | 248 |
| 4 | PaymentScreenSuccessful | 6217807653094995999 | 1564055322 | 248 |
--------------- Общая информация о датафрейме --------------- <class 'pandas.core.frame.DataFrame'> RangeIndex: 244126 entries, 0 to 244125 Data columns (total 4 columns): # Column Non-Null Count Dtype --- ------ -------------- ----- 0 EventName 244126 non-null object 1 DeviceIDHash 244126 non-null int64 2 EventTimestamp 244126 non-null int64 3 ExpId 244126 non-null int64 dtypes: int64(3), object(1) memory usage: 7.5+ MB --------------- Количество явных дубликатов в датафрейме ---------------
413
--------------- Описательная статистика ---------------
| DeviceIDHash | EventTimestamp | ExpId | |
|---|---|---|---|
| count | 244126.00 | 244126.00 | 244126.00 |
| mean | 4627568124591259648.00 | 1564913915.84 | 247.02 |
| std | 2642424998963707904.00 | 177134.32 | 0.82 |
| min | 6888746892508752.00 | 1564029816.00 | 246.00 |
| 25% | 2372212476992240640.00 | 1564756580.25 | 246.00 |
| 50% | 4623191541214045184.00 | 1564919395.00 | 247.00 |
| 75% | 6932517045703054336.00 | 1565074511.00 | 248.00 |
| max | 9222603179720523776.00 | 1565212517.00 | 248.00 |
В таблице 244126 записей (вместе с шапкой таблицы) и 4 колонки:
Пропусков нет.
Нужно удалить явные дубликаты.
Переименуем названия столбцов, поменяем тип данных колонки EventTimestamp на date_time.
# переименуем столбцы
logs.columns = ['event_name', 'user_id', 'event_time', 'group']
# поменяем типы данных
logs['event_time'] = pd.to_datetime(logs['event_time'], unit='s')
# добавим столбец даты и времени
logs['date_time'] = logs['event_time'].dt.date
# удалим дубликаты
logs = logs.drop_duplicates()
display(logs.duplicated().sum())
display(logs)
logs.info()
0
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 0 | MainScreenAppear | 4575588528974610257 | 2019-07-25 04:43:36 | 246 | 2019-07-25 |
| 1 | MainScreenAppear | 7416695313311560658 | 2019-07-25 11:11:42 | 246 | 2019-07-25 |
| 2 | PaymentScreenSuccessful | 3518123091307005509 | 2019-07-25 11:28:47 | 248 | 2019-07-25 |
| 3 | CartScreenAppear | 3518123091307005509 | 2019-07-25 11:28:47 | 248 | 2019-07-25 |
| 4 | PaymentScreenSuccessful | 6217807653094995999 | 2019-07-25 11:48:42 | 248 | 2019-07-25 |
| ... | ... | ... | ... | ... | ... |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
243713 rows × 5 columns
<class 'pandas.core.frame.DataFrame'> Index: 243713 entries, 0 to 244125 Data columns (total 5 columns): # Column Non-Null Count Dtype --- ------ -------------- ----- 0 event_name 243713 non-null object 1 user_id 243713 non-null int64 2 event_time 243713 non-null datetime64[ns] 3 group 243713 non-null int64 4 date_time 243713 non-null object dtypes: datetime64[ns](1), int64(2), object(2) memory usage: 11.2+ MB
# проверим сколько пользователей вошли в разные группы одновременно
logs.groupby('user_id').agg({'group' : 'nunique'}).query('group > 1').count()
group 0 dtype: int64
Таких пользователей нет.
# посмотрим все события в логе
logs['event_name'].drop_duplicates()
0 MainScreenAppear 2 PaymentScreenSuccessful 3 CartScreenAppear 6 OffersScreenAppear 29 Tutorial Name: event_name, dtype: object
# посчитаем количество пользователей
logs['user_id'].drop_duplicates().count()
7551
# посчитаем среднее количество событий на пользователя
logs.groupby('user_id').agg({'event_name': 'count'}).mean()
event_name 32.28 dtype: float64
# выведем все даты, за которые у нас есть данные
logs['date_time'].drop_duplicates()
0 2019-07-25 9 2019-07-26 40 2019-07-27 95 2019-07-28 200 2019-07-29 384 2019-07-30 797 2019-07-31 2828 2019-08-01 39057 2019-08-02 74663 2019-08-03 108014 2019-08-04 141047 2019-08-05 177160 2019-08-06 212982 2019-08-07 Name: date_time, dtype: object
# выведем минимальную и максимальную дату
print('Минимальная дата:', logs['date_time'].min())
print('Максимальная дата:', logs['date_time'].max())
Минимальная дата: 2019-07-25 Максимальная дата: 2019-08-07
# построим столбчатую диаграмму по количеству событий в зависимости от времени в разрезе групп
(logs
.pivot_table(index='date_time', values='event_name', columns='group', aggfunc='count')
.plot(kind='bar', figsize=(15, 10))
)
# Add labels
plt.title('Диаграмма количества событий по датам')
plt.xlabel('Дата')
plt.ylabel('Количество событий')
plt.show()
По диаграмме видно, что в первую неделю данные не полные. Как будто до 2019-08-01 приложением пользовались не все пользователи из наших выборок, а лишь некоторая их часть.\ Поэтому уберем данные за 1 неделю и построим ещё раз данную диаграмму уже с "чистыми" данными.
# посчитаем количество уникальных пользователей до "очищения"
cnt_users_before = logs['user_id'].nunique()
# посчитаем количество событий до "очищения"
cnt_events_before = logs['user_id'].count()
# "очистим" наши данные, взяв данные за период от 1 августа (включительно)
logs = logs.query('event_time >= "2019-08-01"')
# посчитаем изменения количества уникальных пользователей после "очистки"
print('Потеря уникальных пользователей в относительных значениях составляет:', '{:.3%}'.format(1 - (logs['user_id'].nunique() / cnt_users_before)))
print('Потеря уникальных пользователей в абсолютных значениях составляет:', cnt_users_before - logs['user_id'].nunique())
print()
# посчитаем изменения количества событий после "очистки"
print('Потеря событий в относительных значениях составляет:', '{:.3%}'.format(1 - (logs['user_id'].count() / cnt_events_before)))
print('Потеря событий в абсолютных значениях составляет:', cnt_events_before - logs['user_id'].count())
Потеря уникальных пользователей в относительных значениях составляет: 0.225% Потеря уникальных пользователей в абсолютных значениях составляет: 17 Потеря событий в относительных значениях составляет: 1.160% Потеря событий в абсолютных значениях составляет: 2826
В процентном соотношении после очистки данных теряется лишь около 1,2% данных, что в рамках допустимого.\ Далее попробуем построить диаграмму из очищенных данных.
# построим столбчатую диаграмму по количеству событий в зависимости от времени в разрезе групп по очищенным данным
(logs
.pivot_table(index='date_time', values='event_name', columns='group', aggfunc='count')
.plot(kind='bar', figsize=(15, 10))
)
# Add labels
plt.title('Диаграмма количества событий по датам')
plt.xlabel('Дата')
plt.ylabel('Количество событий')
plt.show()
Теперь можно сказать, что у нас полные данные за весь период с 1 августа 2019 года по 7 августа 2019 года.
logs
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2828 | Tutorial | 3737462046622621720 | 2019-08-01 00:07:28 | 246 | 2019-08-01 |
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
240887 rows × 5 columns
# посмотрим, какие события есть в логах и как часто они встречаются. Отсортируем события по частоте.
cnt_events = logs.groupby('event_name').agg({'user_id': 'nunique'})
cnt_events.columns = ['cnt_users']
cnt_events.sort_values(by='cnt_users', ascending=False)
| cnt_users | |
|---|---|
| event_name | |
| MainScreenAppear | 7419 |
| OffersScreenAppear | 4593 |
| CartScreenAppear | 3734 |
| PaymentScreenSuccessful | 3539 |
| Tutorial | 840 |
# посчитаем, сколько пользователей совершали каждое из этих событий. Отсортируем события по числу пользователей.
cnt_events = logs.groupby('event_name').agg({'user_id': 'nunique', 'event_name': 'count'})
cnt_events.columns = ['cnt_users', 'cnt_events']
cnt_events.sort_values(by='cnt_users', ascending=False)
| cnt_users | cnt_events | |
|---|---|---|
| event_name | ||
| MainScreenAppear | 7419 | 117328 |
| OffersScreenAppear | 4593 | 46333 |
| CartScreenAppear | 3734 | 42303 |
| PaymentScreenSuccessful | 3539 | 33918 |
| Tutorial | 840 | 1005 |
# посчитаем долю пользователей, которые совершили действия по данному событию
cnt_events['ratio, %'] = cnt_events['cnt_users'] / logs['user_id'].nunique() * 100
cnt_events = cnt_events.sort_values(by='cnt_users', ascending=False)
cnt_events
| cnt_users | cnt_events | ratio, % | |
|---|---|---|---|
| event_name | |||
| MainScreenAppear | 7419 | 117328 | 98.47 |
| OffersScreenAppear | 4593 | 46333 | 60.96 |
| CartScreenAppear | 3734 | 42303 | 49.56 |
| PaymentScreenSuccessful | 3539 | 33918 | 46.97 |
| Tutorial | 840 | 1005 | 11.15 |
Скорее всего в самом начале появляется экран с обучением, которое можно пропустить. Именно поэтому так мало пользователей с его прохождением, либо тут есть баг. Мне кажется стоит исключить эти данные.
Далее открывается главный экран
Дальше в определенный момент появляется экран с оффером
И если у человека есть желание, то он проходит далее к экрану оплаты
Следующий экран выходит после успешной оплаты
# исключаем события Tutorial из наших данных
cnt_events = cnt_events.query('event_name != "Tutorial"')
logs = logs.query('event_name != "Tutorial"')
display(cnt_events)
logs
| cnt_users | cnt_events | ratio, % | |
|---|---|---|---|
| event_name | |||
| MainScreenAppear | 7419 | 117328 | 98.47 |
| OffersScreenAppear | 4593 | 46333 | 60.96 |
| CartScreenAppear | 3734 | 42303 | 49.56 |
| PaymentScreenSuccessful | 3539 | 33918 | 46.97 |
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
239882 rows × 5 columns
По воронке событий посчитайте, какая доля пользователей проходит на следующий шаг воронки (от числа пользователей на предыдущем). То есть для последовательности событий A → B → C посчитайте отношение числа пользователей с событием B к количеству пользователей с событием A, а также отношение числа пользователей с событием C к количеству пользователей с событием B.
# посчитаем конверсию пользователей от события к событию
cnt_events['conversion, %'] = (cnt_events['cnt_users'] / cnt_events['cnt_users'].shift(1))
cnt_events
/var/folders/m0/hqhjn4g943v5qdg7cp126_600000gn/T/ipykernel_3993/3460090568.py:2: SettingWithCopyWarning: A value is trying to be set on a copy of a slice from a DataFrame. Try using .loc[row_indexer,col_indexer] = value instead See the caveats in the documentation: https://pandas.pydata.org/pandas-docs/stable/user_guide/indexing.html#returning-a-view-versus-a-copy cnt_events['conversion, %'] = (cnt_events['cnt_users'] / cnt_events['cnt_users'].shift(1))
| cnt_users | cnt_events | ratio, % | conversion, % | |
|---|---|---|---|---|
| event_name | ||||
| MainScreenAppear | 7419 | 117328 | 98.47 | NaN |
| OffersScreenAppear | 4593 | 46333 | 60.96 | 0.62 |
| CartScreenAppear | 3734 | 42303 | 49.56 | 0.81 |
| PaymentScreenSuccessful | 3539 | 33918 | 46.97 | 0.95 |
На втором шаге при переходе с главной страницы на страницу с оффером теряется 38% пользователей. Возможно проблема, в том, что не у всех пользователей выходит предложение с оффером или условия вывода страницы оффера затруднительны для среднего пользователя.
# посчитаем долю пользователей, которые доходят с главной страницы до успешной оплаты
cnt_events['funnel, %'] = (cnt_events['cnt_users'] / cnt_events['cnt_users'].values[0])
cnt_events
/var/folders/m0/hqhjn4g943v5qdg7cp126_600000gn/T/ipykernel_3993/1152550264.py:2: SettingWithCopyWarning: A value is trying to be set on a copy of a slice from a DataFrame. Try using .loc[row_indexer,col_indexer] = value instead See the caveats in the documentation: https://pandas.pydata.org/pandas-docs/stable/user_guide/indexing.html#returning-a-view-versus-a-copy cnt_events['funnel, %'] = (cnt_events['cnt_users'] / cnt_events['cnt_users'].values[0])
| cnt_users | cnt_events | ratio, % | conversion, % | funnel, % | |
|---|---|---|---|---|---|
| event_name | |||||
| MainScreenAppear | 7419 | 117328 | 98.47 | NaN | 1.00 |
| OffersScreenAppear | 4593 | 46333 | 60.96 | 0.62 | 0.62 |
| CartScreenAppear | 3734 | 42303 | 49.56 | 0.81 | 0.50 |
| PaymentScreenSuccessful | 3539 | 33918 | 46.97 | 0.95 | 0.48 |
48% пользователей доходят до успешной оплаты.
# визуализируем нашу воронку с помощью графика
stages = cnt_events.index
df_cnt_events = pd.DataFrame(dict(number=cnt_events['cnt_events'], stage=stages))
df_cnt_events['data'] = 'События'
df_cnt_users = pd.DataFrame(dict(number=cnt_events['cnt_users'], stage=stages))
df_cnt_users['data'] = 'Уникальные пользователи'
df = pd.concat([df_cnt_users], axis=0)
fig = px.funnel(df, x='number', y='stage', color='data')
fig.update_layout(title='Воронка', title_x = 0.5)
fig.show()
# посчитаем количество пользователей в каждой группе
logs.groupby('group').agg({'user_id': 'nunique', 'event_name': 'count'})
| user_id | event_name | |
|---|---|---|
| group | ||
| 246 | 2483 | 78985 |
| 247 | 2512 | 76684 |
| 248 | 2535 | 84213 |
# посчитаем количество пользователей которые совершали действия по событиям и разделим их по группам
(logs
.pivot_table(index='event_name', values='user_id', columns='group', aggfunc='count')
.sort_values(by=246, ascending=False)
)
| group | 246 | 247 | 248 |
|---|---|---|---|
| event_name | |||
| MainScreenAppear | 37676 | 39090 | 40562 |
| OffersScreenAppear | 14767 | 15179 | 16387 |
| CartScreenAppear | 14690 | 12434 | 15179 |
| PaymentScreenSuccessful | 11852 | 9981 | 12085 |
# посчитаем количество уникальных пользователей которые совершали действия по событиям и разделим их по группам
(logs
.pivot_table(index='event_name', values='user_id', columns='group', aggfunc='nunique')
.sort_values(by=246, ascending=False)
)
| group | 246 | 247 | 248 |
|---|---|---|---|
| event_name | |||
| MainScreenAppear | 2450 | 2476 | 2493 |
| OffersScreenAppear | 1542 | 1520 | 1531 |
| CartScreenAppear | 1266 | 1238 | 1230 |
| PaymentScreenSuccessful | 1200 | 1158 | 1181 |
Тестов довольно много и нужно сделать коррекцию уровней значимости, чем ниже и займусь.
# сделаем коррекцию уровня значимости по методу Бонферрони
m = 16 # число тестов
alpha = 0.05 # исходный уровень значимости
# считаем поправку
alpha_bonf = alpha / m # добавьте код для расчёта коррекции уровня значимости здесь
# считаем FWER
fwer_bonf = 1 - (1 - alpha_bonf)**(m) # добавьте код для расчёта FWER здесь
print(fwer_bonf)
0.048845042569365726
# сделаем коррекцию уровня значимости по методу Шидака
m = 16 # число тестов
alpha = 0.05 # исходный уровень значимости
# считаем поправку
alpha_sidak = 1 - (1 - alpha)**(1/m)# добавьте код для расчёта коррекции уровня значимости здесь
# считаем FWER
fwer_sidak = 1 - (1 - alpha_sidak) ** m
print(fwer_sidak)
0.04999999999999993
Если брать скорректированный уровень значимости по методам Бонферрони или Шидака, то изменений в тестах не будет, т.к. стандартный уровень значимости 0.05 примерно такой же как и скорректированный по этим двум методам.
# сделаем коррекцию уровня значимости по методу Холма
m, alpha = 16, 0.05 # число тестов и уровень значимости
result = []
for i in range(m): # получаем номер текущего теста и считаем коррекцию
result += [alpha / (m - i)]
print(result)
[0.003125, 0.0033333333333333335, 0.0035714285714285718, 0.0038461538461538464, 0.004166666666666667, 0.004545454545454546, 0.005, 0.005555555555555556, 0.00625, 0.0071428571428571435, 0.008333333333333333, 0.01, 0.0125, 0.016666666666666666, 0.025, 0.05]
Скорректированный уровень значимости по методу Холма может привнести другой эффект на наши тесты. Используем в наших тестах скорректированные уровни значимости по методу Холма.
# создадим функцию для проверки гипотезы о равенстве долей
# alpha = 0.05 # критический уровень статистической значимости
def z_test(group1, group2, event_name, alpha):
group_1 = logs[logs['group'] == group1]
group_2 = logs[logs['group'] == group2]
display('group_1:', group_1)
display('group_2:',group_2)
successes = np.array([group_1[group_1['event_name'] == event_name]['user_id'].nunique(),
group_2[group_2['event_name'] == event_name]['user_id'].nunique()])
print('successes:', successes)
trials = np.array([group_1['user_id'].nunique(),
group_2['user_id'].nunique()])
print('trials:', trials)
print()
# пропорция успехов в первой группе:
p1 = successes[0] / trials[0]
print('Конверсия в первой группе равна:', '{0:.2%}'.format(p1))
# пропорция успехов во второй группе:
p2 = successes[1] / trials[1]
print('Конверсия во второй группе равна:', '{0:.2%}'.format(p2))
print()
# пропорция успехов в комбинированном датасете:
p_combined = (successes[0] + successes[1]) / (trials[0] + trials[1])
print('p_combined:', p_combined)
# разница пропорций в датасетах
difference = p1 - p2
print('difference:', difference)
assert((p_combined * (1 - p_combined) * (1 / trials[0] + 1 / trials[1])) > 0)
# считаем статистику в ст.отклонениях стандартного нормального распределения
z_value = difference / mth.sqrt(p_combined * (1 - p_combined) * (1 / trials[0] + 1 / trials[1]))
print('z_value:', z_value)
# задаем стандартное нормальное распределение (среднее 0, ст.отклонение 1)
distr = st.norm(0, 1)
p_value = (1 - distr.cdf(abs(z_value))) * 2
print()
print('p-значение: ', p_value)
print()
if p_value < alpha:
print('p-value < alpha, поэтому нужно отвергнуть нулевую гипотезу.')
print('Есть основания говорить, что между долями есть существенные различия.')
else:
print('p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу.')
print('Есть основания говорить, что между долями нет существенных различий.')
Сформируем нулевую и альтернативную гипотезы:
# проверим гипотезу о равенстве долей (между группами 246 и 247 по событию посещения главной страницы)
# и посчитаем находят ли статистические критерии различия между ними
z_test(246, 247, "MainScreenAppear", 0.003125)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2834 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:10:26 | 246 | 2019-08-01 |
| 2835 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:10:47 | 246 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244120 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:12:11 | 246 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
78985 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| 2838 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:11:28 | 247 | 2019-08-01 |
| 2839 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:11:30 | 247 | 2019-08-01 |
| 2843 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:12:36 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244088 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:37 | 247 | 2019-08-07 |
| 244089 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:43 | 247 | 2019-08-07 |
| 244090 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:54 | 247 | 2019-08-07 |
| 244091 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:57 | 247 | 2019-08-07 |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
76684 rows × 5 columns
successes: [2450 2476] trials: [2483 2512] Конверсия в первой группе равна: 98.67% Конверсия во второй группе равна: 98.57% p_combined: 0.9861861861861861 difference: 0.0010408356441637956 z_value: 0.31512026353759287 p-значение: 0.7526703436483038 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 246 и 247 по событию получения оффера)
# и посчитаем находят ли статистические критерии различия между ними
z_test(246, 247, "OffersScreenAppear", 0.0033333333333333335)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2834 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:10:26 | 246 | 2019-08-01 |
| 2835 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:10:47 | 246 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244120 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:12:11 | 246 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
78985 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| 2838 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:11:28 | 247 | 2019-08-01 |
| 2839 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:11:30 | 247 | 2019-08-01 |
| 2843 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:12:36 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244088 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:37 | 247 | 2019-08-07 |
| 244089 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:43 | 247 | 2019-08-07 |
| 244090 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:54 | 247 | 2019-08-07 |
| 244091 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:57 | 247 | 2019-08-07 |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
76684 rows × 5 columns
successes: [1542 1520] trials: [2483 2512] Конверсия в первой группе равна: 62.10% Конверсия во второй группе равна: 60.51% p_combined: 0.613013013013013 difference: 0.015927414700216302 z_value: 1.155560508362548 p-значение: 0.24786096925282264 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 246 и 247 по событию оплаты картой)
# и посчитаем находят ли статистические критерии различия между ними
z_test(246, 247, "CartScreenAppear", 0.0035714285714285718)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2834 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:10:26 | 246 | 2019-08-01 |
| 2835 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:10:47 | 246 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244120 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:12:11 | 246 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
78985 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| 2838 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:11:28 | 247 | 2019-08-01 |
| 2839 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:11:30 | 247 | 2019-08-01 |
| 2843 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:12:36 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244088 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:37 | 247 | 2019-08-07 |
| 244089 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:43 | 247 | 2019-08-07 |
| 244090 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:54 | 247 | 2019-08-07 |
| 244091 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:57 | 247 | 2019-08-07 |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
76684 rows × 5 columns
successes: [1266 1238] trials: [2483 2512] Конверсия в первой группе равна: 50.99% Конверсия во второй группе равна: 49.28% p_combined: 0.5013013013013013 difference: 0.017032701350072288 z_value: 1.203775303516804 p-значение: 0.22867643757335676 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 246 и 247 по событию успешной покупки)
# и посчитаем находят ли статистические критерии различия между ними
z_test(246, 247, "PaymentScreenSuccessful", 0.0038461538461538464)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2834 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:10:26 | 246 | 2019-08-01 |
| 2835 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:10:47 | 246 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244120 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:12:11 | 246 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
78985 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| 2838 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:11:28 | 247 | 2019-08-01 |
| 2839 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:11:30 | 247 | 2019-08-01 |
| 2843 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:12:36 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244088 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:37 | 247 | 2019-08-07 |
| 244089 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:43 | 247 | 2019-08-07 |
| 244090 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:54 | 247 | 2019-08-07 |
| 244091 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:57 | 247 | 2019-08-07 |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
76684 rows × 5 columns
successes: [1200 1158] trials: [2483 2512] Конверсия в первой группе равна: 48.33% Конверсия во второй группе равна: 46.10% p_combined: 0.4720720720720721 difference: 0.02229908601419589 z_value: 1.578432523853264 p-значение: 0.11446627829276612 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# выделим самое популярное событие и посчитаем число пользователей, совершивших это событие в каждой из групп
pop_events = (logs
.pivot_table(index='event_name', values='user_id', columns='group', aggfunc='nunique')
.sort_values(by=246, ascending=False)
)
pop_events.head(1)
| group | 246 | 247 | 248 |
|---|---|---|---|
| event_name | |||
| MainScreenAppear | 2450 | 2476 | 2493 |
Самым популярным событием является конечно самое первое событие которое видят пользователи. Это открытие главного экрана приложения.
# посчитаем количество уникальных пользователей в каждой группе
cnt_users = (logs
.groupby('group')
.agg({'user_id': 'nunique'})
)
cnt_users
| user_id | |
|---|---|
| group | |
| 246 | 2483 |
| 247 | 2512 |
| 248 | 2535 |
# посчитаем различие в процентном соотношении между минимальным и максимальным количеством пользователей в группе
100 - (cnt_users['user_id'].min() / cnt_users['user_id'].max() * 100)
2.051282051282058
Различие между группами составляет 2%.
# посчитаем долю пользователей, совершивших событие в каждой из групп
# для этого разделим количество совершивших на общее количество
pop_events['ratio 246, %'] = pop_events[246] / logs[logs['group'] == 246]['user_id'].nunique()
pop_events['ratio 247, %'] = pop_events[247] / logs[logs['group'] == 247]['user_id'].nunique()
pop_events['ratio 248, %'] = pop_events[248] / logs[logs['group'] == 248]['user_id'].nunique()
pop_events
| group | 246 | 247 | 248 | ratio 246, % | ratio 247, % | ratio 248, % |
|---|---|---|---|---|---|---|
| event_name | ||||||
| MainScreenAppear | 2450 | 2476 | 2493 | 0.99 | 0.99 | 0.98 |
| OffersScreenAppear | 1542 | 1520 | 1531 | 0.62 | 0.61 | 0.60 |
| CartScreenAppear | 1266 | 1238 | 1230 | 0.51 | 0.49 | 0.49 |
| PaymentScreenSuccessful | 1200 | 1158 | 1181 | 0.48 | 0.46 | 0.47 |
Получается, что с главного экрана до успешного платежа доходят 46-48% пользователей.
Далее проведем A\B тесты по группам (246 \ 248) и (247 \ 248).
# проверим гипотезу о равенстве долей (между группами 248 и 246 по событию посещения главной страницы)
# и посчитаем находят ли статистические критерии различия между ними
z_test(246, 248, "MainScreenAppear", 0.004545454545454546)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2834 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:10:26 | 246 | 2019-08-01 |
| 2835 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:10:47 | 246 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244120 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:12:11 | 246 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
78985 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2844 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:31 | 248 | 2019-08-01 |
| 2845 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2846 | CartScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2847 | PaymentScreenSuccessful | 4613461174774205834 | 2019-08-01 00:14:43 | 248 | 2019-08-01 |
| 2848 | OffersScreenAppear | 4613461174774205834 | 2019-08-01 00:14:51 | 248 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244082 | MainScreenAppear | 8249271441488197538 | 2019-08-07 21:03:33 | 248 | 2019-08-07 |
| 244084 | OffersScreenAppear | 8249271441488197538 | 2019-08-07 21:03:43 | 248 | 2019-08-07 |
| 244109 | MainScreenAppear | 5317814261427487562 | 2019-08-07 21:09:22 | 248 | 2019-08-07 |
| 244110 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:09:27 | 248 | 2019-08-07 |
| 244115 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:10:08 | 248 | 2019-08-07 |
84213 rows × 5 columns
successes: [2450 2493] trials: [2483 2535] Конверсия в первой группе равна: 98.67% Конверсия во второй группе равна: 98.34% p_combined: 0.9850538062973296 difference: 0.0032776727903590652 z_value: 0.9567144401185823 p-значение: 0.3387114076159288 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 248 и 246 по событию получения оффера)
# и посчитаем находят ли статистические критерии различия между ними
z_test(246, 248, "OffersScreenAppear", 0.005555555555555556)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2834 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:10:26 | 246 | 2019-08-01 |
| 2835 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:10:47 | 246 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244120 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:12:11 | 246 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
78985 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2844 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:31 | 248 | 2019-08-01 |
| 2845 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2846 | CartScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2847 | PaymentScreenSuccessful | 4613461174774205834 | 2019-08-01 00:14:43 | 248 | 2019-08-01 |
| 2848 | OffersScreenAppear | 4613461174774205834 | 2019-08-01 00:14:51 | 248 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244082 | MainScreenAppear | 8249271441488197538 | 2019-08-07 21:03:33 | 248 | 2019-08-07 |
| 244084 | OffersScreenAppear | 8249271441488197538 | 2019-08-07 21:03:43 | 248 | 2019-08-07 |
| 244109 | MainScreenAppear | 5317814261427487562 | 2019-08-07 21:09:22 | 248 | 2019-08-07 |
| 244110 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:09:27 | 248 | 2019-08-07 |
| 244115 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:10:08 | 248 | 2019-08-07 |
84213 rows × 5 columns
successes: [1542 1531] trials: [2483 2535] Конверсия в первой группе равна: 62.10% Конверсия во второй группе равна: 60.39% p_combined: 0.6123953766440813 difference: 0.01707818292594776 z_value: 1.2414900640949729 p-значение: 0.21442476639710506 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 248 и 246 по событию оплаты картой)
# и посчитаем находят ли статистические критерии различия между ними
z_test(246, 248, "CartScreenAppear", 0.0071428571428571435)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2834 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:10:26 | 246 | 2019-08-01 |
| 2835 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:10:47 | 246 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244120 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:12:11 | 246 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
78985 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2844 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:31 | 248 | 2019-08-01 |
| 2845 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2846 | CartScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2847 | PaymentScreenSuccessful | 4613461174774205834 | 2019-08-01 00:14:43 | 248 | 2019-08-01 |
| 2848 | OffersScreenAppear | 4613461174774205834 | 2019-08-01 00:14:51 | 248 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244082 | MainScreenAppear | 8249271441488197538 | 2019-08-07 21:03:33 | 248 | 2019-08-07 |
| 244084 | OffersScreenAppear | 8249271441488197538 | 2019-08-07 21:03:43 | 248 | 2019-08-07 |
| 244109 | MainScreenAppear | 5317814261427487562 | 2019-08-07 21:09:22 | 248 | 2019-08-07 |
| 244110 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:09:27 | 248 | 2019-08-07 |
| 244115 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:10:08 | 248 | 2019-08-07 |
84213 rows × 5 columns
successes: [1266 1230] trials: [2483 2535] Конверсия в первой группе равна: 50.99% Конверсия во второй группе равна: 48.52% p_combined: 0.49740932642487046 difference: 0.024659995662814904 z_value: 1.7467905524022547 p-значение: 0.08067367598823139 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 248 и 246 по событию успешной покупки)
# и посчитаем находят ли статистические критерии различия между ними
z_test(246, 248, "PaymentScreenSuccessful", 0.01)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2829 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:00 | 246 | 2019-08-01 |
| 2830 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:08:55 | 246 | 2019-08-01 |
| 2831 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:08:58 | 246 | 2019-08-01 |
| 2834 | OffersScreenAppear | 3737462046622621720 | 2019-08-01 00:10:26 | 246 | 2019-08-01 |
| 2835 | MainScreenAppear | 3737462046622621720 | 2019-08-01 00:10:47 | 246 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244120 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:12:11 | 246 | 2019-08-07 |
| 244122 | MainScreenAppear | 5849806612437486590 | 2019-08-07 21:13:59 | 246 | 2019-08-07 |
| 244123 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:43 | 246 | 2019-08-07 |
| 244124 | MainScreenAppear | 5746969938801999050 | 2019-08-07 21:14:58 | 246 | 2019-08-07 |
| 244125 | OffersScreenAppear | 5746969938801999050 | 2019-08-07 21:15:17 | 246 | 2019-08-07 |
78985 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2844 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:31 | 248 | 2019-08-01 |
| 2845 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2846 | CartScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2847 | PaymentScreenSuccessful | 4613461174774205834 | 2019-08-01 00:14:43 | 248 | 2019-08-01 |
| 2848 | OffersScreenAppear | 4613461174774205834 | 2019-08-01 00:14:51 | 248 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244082 | MainScreenAppear | 8249271441488197538 | 2019-08-07 21:03:33 | 248 | 2019-08-07 |
| 244084 | OffersScreenAppear | 8249271441488197538 | 2019-08-07 21:03:43 | 248 | 2019-08-07 |
| 244109 | MainScreenAppear | 5317814261427487562 | 2019-08-07 21:09:22 | 248 | 2019-08-07 |
| 244110 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:09:27 | 248 | 2019-08-07 |
| 244115 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:10:08 | 248 | 2019-08-07 |
84213 rows × 5 columns
successes: [1200 1181] trials: [2483 2535] Конверсия в первой группе равна: 48.33% Конверсия во второй группе равна: 46.59% p_combined: 0.4744918294141092 difference: 0.017408635129134487 z_value: 1.234731791642485 p-значение: 0.21693033984516674 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 248 и 247 по событию посещения главной страницы)
# и посчитаем находят ли статистические критерии различия между ними
z_test(247, 248, "MainScreenAppear", 0.004166666666666667)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| 2838 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:11:28 | 247 | 2019-08-01 |
| 2839 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:11:30 | 247 | 2019-08-01 |
| 2843 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:12:36 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244088 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:37 | 247 | 2019-08-07 |
| 244089 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:43 | 247 | 2019-08-07 |
| 244090 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:54 | 247 | 2019-08-07 |
| 244091 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:57 | 247 | 2019-08-07 |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
76684 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2844 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:31 | 248 | 2019-08-01 |
| 2845 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2846 | CartScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2847 | PaymentScreenSuccessful | 4613461174774205834 | 2019-08-01 00:14:43 | 248 | 2019-08-01 |
| 2848 | OffersScreenAppear | 4613461174774205834 | 2019-08-01 00:14:51 | 248 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244082 | MainScreenAppear | 8249271441488197538 | 2019-08-07 21:03:33 | 248 | 2019-08-07 |
| 244084 | OffersScreenAppear | 8249271441488197538 | 2019-08-07 21:03:43 | 248 | 2019-08-07 |
| 244109 | MainScreenAppear | 5317814261427487562 | 2019-08-07 21:09:22 | 248 | 2019-08-07 |
| 244110 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:09:27 | 248 | 2019-08-07 |
| 244115 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:10:08 | 248 | 2019-08-07 |
84213 rows × 5 columns
successes: [2476 2493] trials: [2512 2535] Конверсия в первой группе равна: 98.57% Конверсия во второй группе равна: 98.34% p_combined: 0.9845452744204478 difference: 0.0022368371461952696 z_value: 0.6441218302357536 p-значение: 0.5194964354051703 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 248 и 247 по событию получения оффера)
# и посчитаем находят ли статистические критерии различия между ними
z_test(247, 248, "OffersScreenAppear", 0.005)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| 2838 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:11:28 | 247 | 2019-08-01 |
| 2839 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:11:30 | 247 | 2019-08-01 |
| 2843 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:12:36 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244088 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:37 | 247 | 2019-08-07 |
| 244089 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:43 | 247 | 2019-08-07 |
| 244090 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:54 | 247 | 2019-08-07 |
| 244091 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:57 | 247 | 2019-08-07 |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
76684 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2844 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:31 | 248 | 2019-08-01 |
| 2845 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2846 | CartScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2847 | PaymentScreenSuccessful | 4613461174774205834 | 2019-08-01 00:14:43 | 248 | 2019-08-01 |
| 2848 | OffersScreenAppear | 4613461174774205834 | 2019-08-01 00:14:51 | 248 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244082 | MainScreenAppear | 8249271441488197538 | 2019-08-07 21:03:33 | 248 | 2019-08-07 |
| 244084 | OffersScreenAppear | 8249271441488197538 | 2019-08-07 21:03:43 | 248 | 2019-08-07 |
| 244109 | MainScreenAppear | 5317814261427487562 | 2019-08-07 21:09:22 | 248 | 2019-08-07 |
| 244110 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:09:27 | 248 | 2019-08-07 |
| 244115 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:10:08 | 248 | 2019-08-07 |
84213 rows × 5 columns
successes: [1520 1531] trials: [2512 2535] Конверсия в первой группе равна: 60.51% Конверсия во второй группе равна: 60.39% p_combined: 0.6045175351694075 difference: 0.0011507682257314578 z_value: 0.0835991653262869 p-значение: 0.9333751305879443 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 248 и 247 по событию оплаты картой)
# и посчитаем находят ли статистические критерии различия между ними
z_test(247, 248, "CartScreenAppear", 0.00625)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| 2838 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:11:28 | 247 | 2019-08-01 |
| 2839 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:11:30 | 247 | 2019-08-01 |
| 2843 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:12:36 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244088 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:37 | 247 | 2019-08-07 |
| 244089 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:43 | 247 | 2019-08-07 |
| 244090 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:54 | 247 | 2019-08-07 |
| 244091 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:57 | 247 | 2019-08-07 |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
76684 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2844 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:31 | 248 | 2019-08-01 |
| 2845 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2846 | CartScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2847 | PaymentScreenSuccessful | 4613461174774205834 | 2019-08-01 00:14:43 | 248 | 2019-08-01 |
| 2848 | OffersScreenAppear | 4613461174774205834 | 2019-08-01 00:14:51 | 248 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244082 | MainScreenAppear | 8249271441488197538 | 2019-08-07 21:03:33 | 248 | 2019-08-07 |
| 244084 | OffersScreenAppear | 8249271441488197538 | 2019-08-07 21:03:43 | 248 | 2019-08-07 |
| 244109 | MainScreenAppear | 5317814261427487562 | 2019-08-07 21:09:22 | 248 | 2019-08-07 |
| 244110 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:09:27 | 248 | 2019-08-07 |
| 244115 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:10:08 | 248 | 2019-08-07 |
84213 rows × 5 columns
successes: [1238 1230] trials: [2512 2535] Конверсия в первой группе равна: 49.28% Конверсия во второй группе равна: 48.52% p_combined: 0.4890033683376263 difference: 0.007627294312742616 z_value: 0.5419855498181188 p-значение: 0.5878284605111943 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между группами 248 и 247 по событию успешной покупки)
# и посчитаем находят ли статистические критерии различия между ними
z_test(247, 248, "PaymentScreenSuccessful", 0.008333333333333333)
'group_1:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2832 | MainScreenAppear | 1433840883824088890 | 2019-08-01 00:08:59 | 247 | 2019-08-01 |
| 2833 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:10:15 | 247 | 2019-08-01 |
| 2838 | MainScreenAppear | 4899590676214355127 | 2019-08-01 00:11:28 | 247 | 2019-08-01 |
| 2839 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:11:30 | 247 | 2019-08-01 |
| 2843 | OffersScreenAppear | 4899590676214355127 | 2019-08-01 00:12:36 | 247 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244088 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:37 | 247 | 2019-08-07 |
| 244089 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:43 | 247 | 2019-08-07 |
| 244090 | OffersScreenAppear | 2300292234025330845 | 2019-08-07 21:05:54 | 247 | 2019-08-07 |
| 244091 | MainScreenAppear | 2300292234025330845 | 2019-08-07 21:05:57 | 247 | 2019-08-07 |
| 244121 | MainScreenAppear | 4599628364049201812 | 2019-08-07 21:12:25 | 247 | 2019-08-07 |
76684 rows × 5 columns
'group_2:'
| event_name | user_id | event_time | group | date_time | |
|---|---|---|---|---|---|
| 2844 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:31 | 248 | 2019-08-01 |
| 2845 | MainScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2846 | CartScreenAppear | 4613461174774205834 | 2019-08-01 00:14:34 | 248 | 2019-08-01 |
| 2847 | PaymentScreenSuccessful | 4613461174774205834 | 2019-08-01 00:14:43 | 248 | 2019-08-01 |
| 2848 | OffersScreenAppear | 4613461174774205834 | 2019-08-01 00:14:51 | 248 | 2019-08-01 |
| ... | ... | ... | ... | ... | ... |
| 244082 | MainScreenAppear | 8249271441488197538 | 2019-08-07 21:03:33 | 248 | 2019-08-07 |
| 244084 | OffersScreenAppear | 8249271441488197538 | 2019-08-07 21:03:43 | 248 | 2019-08-07 |
| 244109 | MainScreenAppear | 5317814261427487562 | 2019-08-07 21:09:22 | 248 | 2019-08-07 |
| 244110 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:09:27 | 248 | 2019-08-07 |
| 244115 | OffersScreenAppear | 5317814261427487562 | 2019-08-07 21:10:08 | 248 | 2019-08-07 |
84213 rows × 5 columns
successes: [1158 1181] trials: [2512 2535] Конверсия в первой группе равна: 46.10% Конверсия во второй группе равна: 46.59% p_combined: 0.4634436298791361 difference: -0.004890450885061404 z_value: -0.3483572972992236 p-значение: 0.7275718682261119 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
Далее проведем A+A\B тесты по группам (246+247 \ 248).
# создадим функцию для теста объединенных групп
def z_test_3group(group1, group2, group3, event_name, alpha):
group_1 = pd.concat([logs[logs['group'] == group1], logs[logs['group'] == group2]])
group_2 = logs[logs['group'] == group3]
successes = np.array([group_1[group_1['event_name'] == event_name]['user_id'].nunique(),
group_2[group_2['event_name'] == event_name]['user_id'].nunique()])
trials = np.array([group_1['user_id'].nunique(),
group_2['user_id'].nunique()])
# пропорция успехов в первой группе:
p1 = successes[0] / trials[0]
print('Конверсия в первой группе равна:', '{0:.2%}'.format(p1))
# пропорция успехов во второй группе:
p2 = successes[1] / trials[1]
print('Конверсия во второй группе равна:', '{0:.2%}'.format(p2))
# пропорция успехов в комбинированном датасете:
p_combined = (successes[0] + successes[1]) / (trials[0] + trials[1])
# разница пропорций в датасетах
difference = p1 - p2
assert((p_combined * (1 - p_combined) * (1 / trials[0] + 1 / trials[1])) > 0)
# считаем статистику в ст.отклонениях стандартного нормального распределения
z_value = difference / mth.sqrt(p_combined * (1 - p_combined) * (1 / trials[0] + 1 / trials[1]))
# задаем стандартное нормальное распределение (среднее 0, ст.отклонение 1)
distr = st.norm(0, 1)
p_value = (1 - distr.cdf(abs(z_value))) * 2
print()
print('p-значение: ', '{0:.3f}'.format(p_value))
print()
if p_value < alpha:
print('p-value < alpha, поэтому нужно отвергнуть нулевую гипотезу.')
print('Есть основания говорить, что между долями есть существенные различия.')
else:
print('p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу.')
print('Есть основания говорить, что между долями нет существенных различий.')
# проверим гипотезу о равенстве долей (между объединенными группами 246+247 и 248 по событию посещения главной страницы)
# и посчитаем находят ли статистические критерии различия между ними
z_test_3group(246, 247, 248, "MainScreenAppear", 0.0125)
Конверсия в первой группе равна: 98.62% Конверсия во второй группе равна: 98.34% p-значение: 0.349 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между объединенными группами 246+247 и 248 по событию получения оффера)
# и посчитаем находят ли статистические критерии различия между ними
z_test_3group(246, 247, 248, "OffersScreenAppear", 0.016666666666666666)
Конверсия в первой группе равна: 61.30% Конверсия во второй группе равна: 60.39% p-значение: 0.446 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между объединенными группами 246+247 и 248 по событию оплаты картой)
# и посчитаем находят ли статистические критерии различия между ними
z_test_3group(246, 247, 248, "CartScreenAppear", 0.025)
Конверсия в первой группе равна: 50.13% Конверсия во второй группе равна: 48.52% p-значение: 0.187 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
# проверим гипотезу о равенстве долей (между объединенными группами 246+247 и 248 по событию успешной покупки)
# и посчитаем находят ли статистические критерии различия между ними
z_test_3group(246, 247, 248, "PaymentScreenSuccessful", 0.05)
Конверсия в первой группе равна: 47.21% Конверсия во второй группе равна: 46.59% p-значение: 0.611 p-value > alpha, поэтому нельзя отвергнуть нулевую гипотезу. Есть основания говорить, что между долями нет существенных различий.
В целом было проведено 16 статистических тестов:
A\A тесты:
A\B тесты:
A+A\B тесты:
В данном проекте мы провели исследование о равенстве долей трех групп пользователей мобильного приложения по продаже продуктов питания. Пользователей разбили на 3 группы: 2 контрольные со старыми шрифтами и одну экспериментальную — с новыми, а также соединили пользователей 2х контрольных групп со старыми штрифтами в одну и сравнили доли с экспериментальной группой. Грубо говоря мы провели А+А/В тест.
В тестах, где сравнивались контрольные группы с экспериментальной, т.е. А/В или А+А/В результаты были следующими:
Подытожив можно сказать, что из полученных результатов тестов между всеми группами нет существенных различий. Это говорит о том, что для наши пользователи из 3х групп - не видят существенной разницы между старым и новым шрифтом. В связи с чем предлагаю остановить тест и признать его неуспешным.